package edu.ucsb.android.APMap;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.OutputStream;
import java.net.Socket;
import java.net.UnknownHostException;
import java.util.LinkedList;
import java.util.List;
import android.location.Location;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import edu.ucsb.APMap.util.APInfo;

public class TCPClient{
	int serverPort = 8888;
	String serverIP = "128.111.52.173";
	OutputStream outputStream = null;
	Socket socket = null;
	java.io.InputStream inputStream = null;
	Handler apHandler = null;
	
	public TCPClient(Handler apHandler, boolean wifiConnection) {
		this.apHandler = apHandler;
		if(wifiConnection){
			try {
				socket = new Socket(serverIP, serverPort);
				outputStream = socket.getOutputStream();
				inputStream = (java.io.InputStream) socket.getInputStream();
			} catch (UnknownHostException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}	
	}
	
	private void checkConnection() {
		if (outputStream == null || inputStream == null) {
			Log.d("TCP", "######## connection broken, re-connect");
			try {
				socket = new Socket(serverIP, serverPort);
				outputStream = socket.getOutputStream();
				inputStream = (java.io.InputStream) socket.getInputStream();
				
			} catch (UnknownHostException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		} 
	}
	
	public void sendREQ(Location location) {
		try {
			checkConnection();
			
			if(outputStream!=null){
				double latitude = location.getLatitude();
				double longitude = location.getLongitude();
				
				outputStream.write(("REQ" + ":" + latitude + ":" + longitude + ":").getBytes());
				Log.d("TCP", "############### Send REQ ...");
				byte[] buf = new byte[65536];
				int length = 0;
				if ((length = inputStream.read(buf)) != -1) {
					Log.d("TCP", "############### Received : " + new String(buf, 0, length));
					String wifiString;
					if(buf[0] == 'a'){
						  List<APInfo> info = new LinkedList<APInfo>();
						  wifiString = new String(buf, 2, length-2);
						  if (wifiString.trim().length() > 0) {
							  String[] aps = wifiString.split(";");
							  for(String ap: aps){
								  Log.d("ap info", "###### " + ap);
								  String[] items = ap.split(",");
								  //public APInfo(String bSSID, String sSID, String capabilities, double frequency, double longtitude, double latitude)
								  //apInfos += bssid + ", " + ssid + ", " + capabilities + ", " + frequency + ", " + longtitude + ", " + latitude + ";";
								  APInfo oneAp = new APInfo(items[0], items[1], items[2], Double.parseDouble(items[3]), Double.parseDouble(items[4]) , Double.parseDouble(items[5]));
								  info.add(oneAp);
							  }
							  Message msg = new Message();
							  msg.obj = info;
							  apHandler.sendMessage(msg);
						  }
					  }
					
				}
			}
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	public void sendFile(String fileName){
		int len = 0;
		int fileSize = 0;
		int remainingSize = 0;
		byte[] buf = new byte[1024];
		checkConnection();
		if (outputStream != null && inputStream != null) {
			try {
				File file = new File(fileName);
				FileInputStream fis = new FileInputStream(file); 
				fileSize = (int) file.length();
				remainingSize = fileSize;
				Log.d("send file", "######### file size " + fileSize);
				
				buf[0] = 'T'; buf[1] = 'R'; buf[2] = 'A';
				buf[3] = ':';
				buf[4] = (byte)(fileSize >>> 24);
				buf[5] = (byte)(fileSize >>> 16);
				buf[6] = (byte)(fileSize >>> 8);
				buf[7] = (byte)fileSize;
				buf[8] = ':';
				
				if(remainingSize > buf.length-9){
					len = fis.read(buf, 9, buf.length-9);
				}
				else{
					len = fis.read(buf, 9, remainingSize);
				}
				remainingSize -= len;	
				len += 9;
				
				while (len > 0) 
				{
					outputStream.write(buf, 0, len);
					Log.d("TCP", "########## send " + len + "bytes");
					if(remainingSize > buf.length){
						len = fis.read(buf, 0, buf.length);
					}
					else{
						len = fis.read(buf, 0, remainingSize);
					}
					remainingSize -= len;
				}
						
					Log.d("TCP", "############### done!");
					
				fis.close();
			} catch (FileNotFoundException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
}
